home *** CD-ROM | disk | FTP | other *** search
/ Collection of Tools & Utilities / Collection of Tools and Utilities.iso / asmutil / zeno25.zip / ZENO.ASM next >
Assembly Source File  |  1990-01-19  |  14KB  |  421 lines

  1. Page 60,132
  2. ; ZENO:  June 11, 1986  «RM120»«IP0,6»
  3. ;   Modified Sept 4, 1986 by R Tansky to fix 40-character mode
  4. ;   Modified Oct 31, 1986 by R Tansky to further fix 40-character mode and to
  5. ;    fix graphics mode
  6. ;   Modified Jan 28, 1987 by C Blum to add code to support TTY mode call
  7. ;    (AH=0Eh).  Required by some clone BIOS implementations (DTK/ERSO for
  8. ;    one) because they do not issue any 'set    cursor' calls from within the
  9. ;    TTY mode call.  This causes ZENO to lose its video offset and the
  10. ;    display goes out to lunch.
  11. ;   Modified May 29, 1987 by Lynn Ransdell to support KEDIT 3.51
  12. ;   Modified Dec 13, 1988 by Glenn K. Smith to do snow suppression and to add
  13. ;    a /S option to enable this suppression.  Use of this switch causes
  14. ;    ZENO to be around 2 1/2 times slower (ZENOTEST=66 @10mhz).
  15. ;   Modified Jan 15, 1988 by Glenn K. Smith to speed up snow checking and to
  16. ;    fix a bug.  Some programs didn't work right with ZENO.  Mainly those
  17. ;    which modified the cursor position without calling ZENO (Procomm+,
  18. ;    Turbo Pascal CRT unit and others).  The fix required calculating the
  19. ;    screen offset using the BIOS cursor everytime a character was placed
  20. ;    on the screen.  ZENOTEST now takes 46 seconds @10mhz instead of 66.]
  21. ;   Modified Jan 19, 1989 by Howard Flank to work correctly with AMI 386 BIOS.
  22. ;    Rewrote the command line scanner, accepts upper/lower, switches may be
  23. ;    preceeded by slash, dash, or space, etc.  Changed the /K switch to the
  24. ;    more standard /U switch.  Put cursor recalc code for ERSO BIOS on /E
  25. ;    switch.  Added /H switch to display a help screen.  'Prettied' up the
  26. ;    messages.  Made redundant code into subroutines.  Changed 'kill' code
  27. ;    for compatibility with TopView and moved 'kill' message out of resident 
  28. ;    code.  Resident code is 200 bytes smaller.
  29.  
  30. cseg        segment    para public 'code'
  31. zeno        proc    far
  32.         assume    cs:cseg, ds:cseg, es:cseg, ss:cseg
  33.         org    100h        ; for .COM file
  34.  
  35. ;------------------------------*
  36. ;  ENTER HERE ON INITIAL LOAD  *
  37. ;------------------------------*
  38. start:        jmp    near ptr load_pgm
  39.  
  40. CR        equ    0Dh
  41. LF        equ    0Ah
  42. video_vector    dd    0
  43. core_seg    dw    0
  44. bios_cursor_pos label    dword
  45. bios_ofst    dw    00h        ; offset for active page
  46.         dw    40h        ; segment for bios data
  47. crt_mode    db    2        ; passes if 4, 5, or 6
  48. active_page    db    0
  49. cursor_type    dw    0B0Ch        ; DOS cursor
  50. video_posn    label    dword
  51. video_ofst    dw    0        ; offset against video_seg
  52. video_seg    dw    0
  53. video_addr    dw    0
  54. onesixty    db    160
  55. snow        db    0        ; Snow suppression flag
  56. recalc        db    0
  57.  
  58. ;---------------------------*
  59. ;  ENTER HERE FROM INT 10H  *
  60. ;---------------------------*
  61. video_int:    sti                ; interrupts on
  62.         pushf                ; save flags
  63.         cmp    cs:crt_mode,3        ; check for color text 1
  64.         je    video_keep        ; go if so
  65.         cmp    cs:crt_mode,2        ; check for color text 2
  66.         je    video_keep        ; go if so
  67.         cmp    cs:crt_mode,7        ; check for b/w
  68.         je    video_keep        ; go if so
  69.         cmp    ah,0            ; check for set mode
  70.         je    video_keep        ; if so, continue
  71.         jmp    short video_rtn        ; go if graphics / 40 col
  72. video_keep:    push    ds            ; save regs
  73.         push    es
  74.         push    di
  75.         push    ax
  76.         push    cx
  77.         push    dx
  78.         push    cs            ; set ds for addressibility
  79.         pop    ds
  80.         cmp    recalc,3        ; ERSO cursor recalc req'd?
  81.         jne    video_func        ; no:
  82.         les    di,bios_cursor_pos    ; yes: recalc
  83.         push    ax
  84.         push    cx
  85.         mov    ax,es:[di]
  86.         call    calc_offset        ; calc offset into video ram
  87.         and    recalc,0FEh        ; clear recalc flag
  88.         pop    cx
  89.         pop    ax
  90. video_func:    cmp    ah,1            ; to set type
  91.         je    $set_type
  92.         cmp    ah,0            ; to set mode
  93.         je    $set_mode
  94.         cmp    ah,5            ; to set page
  95.         je    $set_page
  96.         cmp    ax,0F0F0h        ; uninstall code
  97.         je    $remove            ; go if found
  98.         cmp    bh,active_page        ; check if active page
  99.         jne    video_exit        ; no: use BIOS
  100.         cmp    ah,14            ; to write as TTY
  101.         je    $TTY
  102.         cmp    ah,2            ; to set cursor
  103.         je    set_cursor
  104.         cmp    ah,3            ; to read cursor
  105.         je    $read_cursor
  106.         cmp    cx,1            ; check multiple write
  107.         jne    video_exit        ; yes: use BIOS
  108.         cmp    ah,10            ; to write char only
  109.         je    write_char
  110.         cmp    ah,9            ; to write char/attr
  111.         je    $write_both
  112. video_exit:    pop    dx            ; restore regs
  113.         pop    cx
  114.         pop    ax
  115.         pop    di
  116.         pop    es
  117.         pop    ds
  118. video_rtn:    popf                ; restore flags
  119.         jmp    cs:dword ptr video_vector ; hand off interrupt to BIOS
  120.  
  121. $TTY:        jmp    TTY
  122. $write_both:    jmp    write_both
  123. $read_cursor:    jmp    read_cursor
  124. $set_page:    jmp    set_page
  125. $set_type:    jmp    set_type
  126. $set_mode:    jmp    set_mode
  127. $remove:    jmp    remove
  128.  
  129. write_char:    Call    Display1
  130.         jmp    zeno_exit
  131.  
  132. set_cursor:    add    video_ofst,2        ; for next char
  133.         les    di,bios_cursor_pos    ; get bios
  134.         inc    byte ptr es:[di]    ; assume next
  135.         cmp    es:[di],dx        ; check if next
  136.         je    offset_ready        ; go if next
  137.         mov    ax,dx            ; get req posn
  138.         mov    es:[di],ax        ; save req posn
  139.         call    calc_offset        ; calc offset into video ram
  140. offset_ready:    mov    cx,video_ofst        ; offset in cx
  141.         shr    cx,1            ; for byte count
  142.         mov    ah,14            ; cursor MSB register
  143.         mov    dx,video_addr        ; 6845 index addr
  144.         mov    al,ah            ; get register
  145.         out    dx,al            ; send register
  146.         inc    dx            ; 6845 data addr
  147.         mov    al,ch            ; get cursor MSB
  148.         out    dx,al            ; send cursor MSB
  149.         dec    dx            ; 6845 index addr
  150.         mov    al,ah            ; cursor MSB register
  151.         inc    al            ; cursor LSB register
  152.         out    dx,al            ; send register
  153.         inc    dx            ; 6845 data addr
  154.         mov    al,cl            ; get cursor LSB
  155.         out    dx,al            ; send cursor LSB
  156.         jmp    zeno_exit
  157.  
  158. write_both:    mov    ah,bl            ; get attribute
  159.         push    ax
  160.         les    di,bios_cursor_pos
  161.         mov    ax,es:[di]
  162.         Call    Calc_Offset
  163.         les    di,video_posn        ; get screen position
  164.         cmp    snow,1            ; Snow suppression?
  165.         je    color            ; yes:
  166.         pop    ax
  167.         stosw                ; Place char+attr onto screen
  168.         jmp    short zeno_exit
  169. color:        mov    dx,03DAh
  170.         cli
  171. WaitNoH1:    in    al, dx          ; Get 6845 Status
  172.         test    al,8            ; Check vert retrace
  173.         jnz    WaitE1          ;   In Progress? go
  174.         rcr    al,1            ; Wait for end of
  175.         jc    WaitNoH1        ;   horizontial retrace
  176. WaitH1:        in    al,dx            ; Get 6845 status again
  177.         rcr    al,1            ; Wait for horizontial
  178.         jnc    WaitH1            ;   retrace
  179. WaitE1:        pop    ax
  180.         stosw
  181.         sti
  182.  
  183. zeno_exit:    pop    dx            ; restore regs
  184.         pop    cx
  185. zeno_exit2:    pop    ax
  186.         pop    di
  187.         pop    es
  188.         pop    ds
  189.         popf                ; restore flags
  190.         iret                ; return from interrupt
  191.  
  192. set_recalc:    or    recalc,1        ; set cursor pos recalc, then
  193. $video_exit:    jmp    video_exit        ; use BIOS routines
  194.  
  195. read_cursor:    pop    dx            ; pop regs off stack
  196.         pop    cx
  197.         les    di,bios_cursor_pos    ; get bios
  198.         mov    dx,es:[di]        ; get bios cursor posn
  199.         mov    cx,cursor_type        ; get type
  200.         jmp    short zeno_exit2
  201.  
  202. set_page:    mov    active_page,al        ; save page
  203.         xor    ah,ah            ; page in ax
  204.         shl    ax,1            ; for word count
  205.         add    ax,50h            ; offset for page zero
  206.         mov    bios_ofst,ax        ; save offset
  207.         jmp    video_exit        ; pass to bios
  208.  
  209. set_type:    mov    cursor_type,cx        ; save type
  210.         jmp    video_exit        ; pass to bios
  211.  
  212. set_mode:    mov    crt_mode,al        ; save mode
  213.         mov    video_ofst,0        ; top left
  214.         jmp    video_exit        ; done
  215.  
  216. TTY:        cmp    al,' '            ; control characters?
  217.         jb    set_recalc        ; yes: set for recalc, use BIOS
  218.         cmp    video_ofst,25*80*2-2    ; scroll imminent ?
  219.         jnb    set_recalc        ; yes: set for recalc, use BIOS
  220.         Call    Display1        ; display w/ or w/o snow
  221.         les    di,bios_cursor_pos    ; get bios
  222.         mov    dx,es:[di]        ; get current pos
  223.         inc    dl            ; next char pos
  224.         cmp    dl,79            ; new line ?
  225.         ja    TTY_new_line        ; yes, adjust
  226.         jmp    set_cursor        ; set cursor
  227. TTY_new_line:    mov    dl,0            ; col = 1
  228.         inc    dh            ; inc row
  229.         jmp    set_cursor        ; set cursor
  230.  
  231. ;---- SUBROUTINE: DISPLAY A CHAR W/ OR W/O SNOW SUPPRESSION -------------------
  232. Display1    Proc
  233.         push    ax
  234.         les    di,bios_cursor_pos
  235.         mov    ax,es:[di]
  236.         Call    Calc_Offset
  237.         les    di,video_posn        ; get screen position
  238.         cmp    snow,1
  239.         je    SuppressSnow
  240.         pop    ax
  241.         stosb
  242.         ret
  243. SuppressSnow:    mov    dx,03DAh        ; Put char, snow suppressed
  244.         cli
  245. WaitNoH:    in    al, dx            ; Get 6845 Status
  246.         test    al,8            ; Check vert retrace
  247.         jnz     WaitE            ;   In Progress? go
  248.         rcr     al,1            ; Wait for end of
  249.         jc      WaitNoH            ;   horizontial retrace
  250. WaitH:        in      al, dx            ; Get 6845 status again
  251.         rcr     al, 1            ; Wait for horizontial
  252.         jnc     WaitH            ;   retrace
  253. WaitE:        pop    ax
  254.         stosb
  255.         sti
  256.         ret
  257. Display1    EndP
  258.  
  259. ;---- SUBROUTINE: CALC THE VIDEO OFFSET FROM THE CURSOR POSITION (In AX) ------
  260. Calc_Offset    Proc
  261.         mov    cx,ax            ; copy posn
  262.         mov    al,ah            ; rows in al
  263.         mul    onesixty